Gérer son environnement logiciel avec Guix...

...en 3.5 commandes

Café Guix, 25/10/2022
pierre-antoine.bouttier@univ-grenoble-alpes.fr

Qu'est-ce que Guix ?

  • Une distribution...
  • ...mais aussi un gestionnaire de paquets (APT, brew, )...
  • ...Ou, plus précisément, un gestionnaire d'environnement logiciel (e.g. module, conda, spack, Nix :))

Pourquoi Guix ?

  • Fait pour la reproductibité logicielle, par construction
    • Comme Nix
    • Au contraire de Spack, conda, modules, très dépendant du système hôte
  • Pour le HPC :
    • Pas besoin des droits administrateur pour mettre en place n'importe quel environnement logiciel
    • Communauté française active
    • Interface et langage relativement explicite (amha, plus que Nix)

Pour aller plus loin

Quelques articles/présentations qui explicitent les points ci-dessus

Deux termes et définitions basiques

  • Un paquet GUIX : Une définition (=code source, fichier texte brut) de l'ensemble des instructions et dépendances pour installer un logiciel
  • Un channel Guix : un dépôt git contenant un ensemble de définitions de paquets (et quelques fichiers de configurations). Un numéro de comit particulier (donc un état bien identifié des définitions) de ce dépôt peut être appelé révision.

La reproductibilité de l'environnement logiciel avec GUIX

Au-delà des mécanismes internes de GUIX pour assurer la reproductibilité logicielle, en tant qu'utilisateur, puisque les paquets que vous avez installés (et toutes leurs dépendances) correspondent à un état des définitions bien identifiées (par le numéro de commit du channel sur lequel vous pointez au moment d'installer le paquet), il est facile, sur une autre machine et à un autre moment, de réinstaller ce même environnement en indiquant cet état des définitions (=n° de commit du channel).

Passons à la pratique

Prérequis :

  • Une machine avec les commandes guix disponibles
  • Accès à internet depuis cette machine
  • C'est tout.

Les premiers pas

Vous avez besoin d'installer un logiciel sans trop connaître le nom de sa définition GUIX ?

guix search nom_approximatif

  • guix search donne plein d'info sur les paquets : nom, version, dépendances

Les premiers pas

Vous voulez installer un logiciel ?

guix install nom_définition_GUIX

Pour connaître les paquets que vous avez installés :

guix package -I

Pour en supprimer :
guix remove nom_définition_GUIX

État des définitions

Les versions des logiciels que vous installés dépendent de celles renseignées dans leurs définitions !

Pour connaître l'état des définitions (numéro de commit du channel/dépôt git dans lequel elles sont versionnées):
guix describe

Pour accéder à des versions récentes des logiciels, il faut mettre à jour ces définitions :
guix pull

Cas pratique

Lancement d'un script python3 utilisant numpy.

Nous avons besoin :

  • Du script !
  • D'un interpréteur python3 et de numpy
  • guix search numpy et guix install ...
  • Cf. démo

Oublions tout et utilisons guix shell

guix shell permet de lancer, à la volée, un environnement logiciel précis, avec différents niveau d'isolation du système hôte, (ici, très isolé) :

guix shell -C python python-numpy 
  • Rien n'est installé dans votre espace utilisateur, en quittant le shell, il ne restera plus de trace de l'environnement (cf conteneurs)

Décrivons notre envrionnement logiciel une bonne fois pour toute

Plutôt que de rentrer à la main, à chaque fois, la liste des paquets de votre environnement, nous pouvons les lister dans une fichier texte, donc versionnable dans le dépôt de votre code source.

Par convention, on nomme ce fichier manifest.scm qui contient, pour notre exemple :

(specifications->manifest
  (list "python"
        "python-numpy"))

Il suffit ensuite d'indiquer ce fichier à la commande guix shell:

guix shell -C -m manifest.scm

Comment être sûr de fixer la version de mes dépendances ?

En identifiant précisément l'état de mes définitions !

  • Les définitions sont dans des channels, i.e. des dépôts git

  • Il faut donc lister les dépôts git correspondant à nos dépendances et le numéro de commit de ceux-ci sur lequel on pointe : guix describe -f channels >> channels.scm

  • Nous avons une deuxième fichier texte, channels.scm à versionner au côté de notre code !

Récapitulons

Pour décrire avec précision notre environnement logiciel, nous avons besoin de 2 fichiers dans le dpôt Git de notre code :

  • manifest.scm qui liste les dépendances de notre code
  • channels.scmqui liste les channels utilisés et leur état

Comment fais-je pour déployer cet environnement ailleurs et/ou à un autre moment ?

  • On clone le dépôt du code (scripts, doc, manifest.scm, channels.scm)
  • On lance la commande suivante :
guix time-machine -C channels.scm -- shell -C -m manifest.scm
  • guix time-machine donne accès à d'autres révisions de guix et lance la commande guix indiquée apprès -- dans cette révision.
  • Nous déployons ici bien l'environnement logiciel indiqué dans l'état spécifié.
  • C'est tout !

Comment fais-je pour déployer l'environnement logiciel sur une machine sans guix ?

  • Une machine sans les commandes guix disponibles ne pourra pas exécuter guix time-machineou guix shell.
  • Mais, elle peut exécuter des conteneurs.
  • Ça tombe bien, Guix permet de créer des images de conteneurs à partir de manifest.scm et channels.scm (sur une machine où guixest disponible):
guix time-machine -C channels.scm -- pack --format=squashfs -m manifest.scm
  • Ici, l'image créée est au format reconnu par singularity, on peut créer une image docker-ready ou un simple tar.gz.
  • Il reste à la copier sur la machine cible sans guix puis à l'exécuter
  • cf. démo

Too Long; Did not Read

  • Sur une machine avec guix :

    • On créée le manifest.scm contenant la liste de nos dépendances
    • guix describe -f channels >> channels.scm pour noter l'état des définitions de paquets qui nous conviennent.
    • On versionne les deux ficheirs à côté de notre code source
  • Pour déployer sur une machine cible avec guix, on exécute sur la machine cible :

    • guix time-machine -C channels.scm -- shell -C -m manifest.scm
  • Pour dployer sur un machine cible sans guix

    • Sur la machine source avec guix : guix time-machine -C channels.scm -- pack --format=squashfs -m manifest.scm
    • On transfère l'image ainsi créée sur la machine cible que l'one exécute (ici avec singularity)

Quelques remarques/limites

  • Ici, tout est simple parce que nous partons du présupposé que les dépendances dont nous avons besoin ont leur définition dans Guix. Si elles ne l'ont pas, il faut faire remonter le besoin (ou si vous vous en sentez capable, écrivez-les :))
  • Sauf cas particulier (fonctionnalités), ne vous attachez pas au numéro de versions de vos dépendances logicielles. Faites les tests avec les versions disponibles dans Guix et si ça marche, partez de la révision Guix testée.
  • Certains logiciels sont réellement difficiles à empaqueter pour Guix (e.g. softs propriétaires ou avec des dépendances de logicielles propriétaires). Dans la grande majorité des cas, ces logiciels vous éloignent de la reproductibilité par design.

Pourquoi Guix plutôt qu'autre chose ?

  • Parce qu'avant de garantir la reproductibilité, c'est diablement pratique et efficace !
    • Virtualenv mais pour tous les écosystèmes
    • Le voyage dans le temps et l'espace robuste et fiable...
    • ...peu importe le système hôte
  • Et c'est, avec Nix, le seul gestionnaire d'env. log. permettant, simplement, de renforcer significativement la reproductibilité de nos/vos travaux numériques.
  • La reproductibilité logicielle ne garantit pas la reproductibilité bit-à-bit (e.g. float comp.) d'une machine à l'autre. Mais si ce n'est aps une condition suffisante, cc'est une condition nécessaire. Guix la permet, sans que ce soit compliqué.